package com.xiaobawang.xjsyy_idea_plugin.panel.dev_process.view;

import com.intellij.ui.JBColor;
import com.xiaobawang.xjsyy_idea_plugin.forest.RunningDetail;
import com.xiaobawang.xjsyy_idea_plugin.panel.dev_process.struct.*;
import com.xiaobawang.xjsyy_idea_plugin.service.Service;
import com.xiaobawang.xjsyy_idea_plugin.util.DateUtil;
import lombok.Data;
import lombok.EqualsAndHashCode;

import javax.swing.*;
import javax.swing.Timer;
import javax.swing.border.Border;
import java.awt.*;
import java.awt.event.*;
import java.util.List;

/**
 * @author synhard
 * @description TODO
 * @date 2024/5/16 15:13
 * @email songxinhang2023@e-chinalife.com
 * @id 18101119
 * @phone 13001321080
 */
@EqualsAndHashCode(callSuper = true)
@Data
public class RunningPanel extends JPanel {
    // 定时器
    private Timer dataFetchTimer;
    // 北部的运行按钮
    private JButton runningBtn;
    // 中部的流水线区域
    private JPanel pipeLinePanel;
    // 设置为边界布局
    private BorderLayout borderLayout;
    // 绑定数据
    private DevProcess devProcess;
    // 流水线id
    private Long pipelineId;
    // 流水线运行id
    private Long pipelineRunId;
    // 数据变化flag
    private Boolean dataChangedFlag;
    // 父panel
    private DevProcessPanel devProcessPanel;

    public RunningPanel(DevProcess devProcess, DevProcessPanel devProcessPanel) {
        this.devProcess = devProcess;
        this.borderLayout = new BorderLayout();
        this.devProcessPanel = devProcessPanel;
        this.dataChangedFlag = false;
        setLayout(borderLayout);
        initPipelinePanel();
        initRunningBtn();
        initTimer();
    }

    private void initTimer() {
        // 初始化定时器
        this.dataFetchTimer = new javax.swing.Timer(5000, e -> {
            updateDevProcess();
        });
    }

    /**
     * @param
     * @author synhard
     * @description 初始化运行按钮
     * @date 2024/6/5 15:37
     */
    private void initRunningBtn() {
        this.runningBtn = new JButton("运行");
        // 为运行按钮设置点击事件
        this.runningBtn.addActionListener(e -> {
            runningBtn.setEnabled(false); // 禁用按钮
            // 点击按钮时，创建并显示新的窗口
            RunningConfigDialog runningConfigDiaLog = new RunningConfigDialog(this);
            Dimension           screenSize          = Toolkit.getDefaultToolkit().getScreenSize();
            int                 x                   = (int) ((screenSize.getWidth() - runningConfigDiaLog.getWidth()) / 2);
            int                 y                   = (int) ((screenSize.getHeight() - runningConfigDiaLog.getHeight()) / 2);

            runningConfigDiaLog.setLocation(x, y);
            runningConfigDiaLog.setVisible(true);

            // 添加监听器以便在对话框关闭时重新启用按钮
            runningConfigDiaLog.addWindowListener(new WindowAdapter() {
                @Override
                public void windowClosed(WindowEvent e) {
                    runningBtn.setEnabled(true); // 对话框关闭后重新启用按钮
                }
            });
        });
        add(runningBtn, BorderLayout.SOUTH);
    }

    /**
     * @param
     * @author synhard
     * @description 初始化流水线面板
     * @date 2024/6/5 15:37
     */
    private void initPipelinePanel() {
        this.pipeLinePanel = new JPanel();
        // 根据研发流程的各个阶段获取表格的尺寸并绘制
        int[]      scope      = getGridScope(devProcess);
        GridLayout gridLayout = new GridLayout(scope[0], scope[1]);
        gridLayout.setHgap(10);
        gridLayout.setVgap(10);
        this.pipeLinePanel.setLayout(gridLayout);
        JPanel[][] panels = buildPanel(devProcess, scope[0], scope[1]);
        for (JPanel[] panel : panels) {
            for (int j = 0; j < panels[0].length; j++) {
                if (panel[j] != null) {
                    this.pipeLinePanel.add(panel[j]);
                } else {
                    this.pipeLinePanel.add(new JPanel());
                }
            }
        }
        add(pipeLinePanel, BorderLayout.CENTER);
    }

    private void updateDevProcess() {
        // 调用云效获取新的研发流程
        RunningDetail runningDetail = Service.runningDetail(pipelineId, pipelineRunId);
        updateDevProcessWithRunningDetail(runningDetail);
        this.devProcessPanel.runningPanel = new RunningPanel(this.devProcess, this.devProcessPanel);
        this.devProcessPanel.updateContentPanel(this.devProcessPanel.runningPanel);
        // 如果状态为运行完成，则关闭定时器
        if ("FAIL".equals(runningDetail.getStatus()) ||
                "SUCCESS".equals(runningDetail.getStatus()) ||
                "CANCELED".equals(runningDetail.getStatus())) {
            this.dataFetchTimer.stop();
        }
    }

    private void updateDevProcessWithRunningDetail(RunningDetail runningDetail) {
        List<RunningDetail.Stage> stages  = runningDetail.getStages();
        List<PipelineStage>       pipelineStageList = devProcess.getPipeline().getPipelineStageList();
        for (int i = 0; i < pipelineStageList.size(); i++) {
            // 设置阶段状态
            RunningDetail.StageInfo stageInfo     = stages.get(i).getStageInfo();
            PipelineStage           pipelineStage = pipelineStageList.get(i);
            pipelineStage.setStatus(stageInfo.getStatus());
            // 设置任务状态
            List<RunningDetail.Job> jobs                 = stageInfo.getJobs();
            List<PipelineStageJob>  pipelineStageJobList = pipelineStage.getPipelineStageJobList();
            for (int j = 0; j < pipelineStageJobList.size(); j++) {
                RunningDetail.Job job              = jobs.get(j);
                PipelineStageJob  pipelineStageJob = pipelineStageJobList.get(j);
                Long              startTime        = job.getStartTime();
                if (startTime != null) {
                    pipelineStageJob.setStartTime(DateUtil.parseTimestampToDateStr(startTime));
                }
                Long endTime = job.getEndTime();
                if (endTime != null) {
                    pipelineStageJob.setEndTime(DateUtil.parseTimestampToDateStr(endTime));
                }
                pipelineStageJob.setResultStatus(job.getStatus());
            }
        }
    }

//    private void updateDevProcess() {
//        // 调用云效获取新的研发流程
//        ApplicationManager.getApplication().invokeLater(this::updateDevProcessWithRunningDetail);
//        this.devProcessPanel.updateContentPanel(new RunningPanel(this.devProcess, this.devProcessPanel));
//    }
//
//    private void updateDevProcessWithRunningDetail() {
//        List<PipelineStage> pipelineStageList = devProcess.getPipeline().getPipelineStageList();
//        for (PipelineStage pipelineStage : pipelineStageList) {
//            // 设置阶段状态
//            pipelineStage.setStatus("RUNNING");
//            // 设置任务状态
//            List<PipelineStageJob> pipelineStageJobList = pipelineStage.getPipelineStageJobList();
//            for (PipelineStageJob pipelineStageJob : pipelineStageJobList) {
//                pipelineStageJob.setStartTime(new Date().toString());
//                pipelineStageJob.setEndTime(new Date().toString());
//                pipelineStageJob.setResultStatus(String.valueOf(new Random().nextInt()));
//            }
//        }
//    }

    /**
     * @description 构造每个单元格对应的 panel
     * @author synhard
     * @date 2024/5/16 15:35
     * @email songxinhang2023@e-chinalife.com
     * @id 18101119
     * @phone 13001321080
     */
    private JPanel[][] buildPanel(DevProcess devProcess, int row, int col) {
        JPanel[][]          panels            = new JPanel[row][col];
        Pipeline            pipeline          = devProcess.getPipeline();
        List<CodeSource>    codeSourceList    = pipeline.getCodeSourceList();
        List<PipelineStage> pipelineStageList = pipeline.getPipelineStageList();

        for (int i = -1; i < codeSourceList.size(); i++) {
            if (i == -1) {
                JPanel head  = new JPanel();
                JLabel label = new JLabel("流水线源");
                Font   font  = new Font("黑体", Font.PLAIN, 20);
                label.setFont(font);
                head.add(label);
                panels[i + 1][0] = head;
                continue;
            }
            CodeSource codeSource = codeSourceList.get(i);
            JPanel     panel      = new JPanel(new GridLayout(4, 1));
            panel.add(new JLabel(codeSource.getName()));
            panel.add(new JLabel(codeSource.getBranch()));
            panel.add(new JLabel(codeSource.getEndpoint()));
            panel.add(new JLabel(codeSource.getType()));
            Border border = BorderFactory.createLineBorder(JBColor.BLUE, 3); // 蓝色边框，宽度为3
            panel.setBorder(border);
            panels[i + 1][0] = panel;
        }

        for (int i = 0; i < pipelineStageList.size(); i++) {
            PipelineStage pipelineStage = pipelineStageList.get(i);
            JPanel        head          = new JPanel();
            JLabel        label         = new JLabel(pipelineStage.getName());
            Font          font          = new Font("黑体", Font.PLAIN, 20);
            label.setFont(font);
            head.add(label);
            panels[0][i + 1] = head;
            List<PipelineStageJob> pipelineStageJobList = pipelineStage.getPipelineStageJobList();
            for (int j = 0; j < pipelineStageJobList.size(); j++) {
                PipelineStageJob pipelineStageJob = pipelineStageJobList.get(j);
                JPanel           panel            = new JPanel(new GridLayout(4, 1));
                panel.add(new JLabel(pipelineStageJob.getName()));
                panel.add(new JLabel(pipelineStageJob.getStartTime()));
                panel.add(new JLabel(pipelineStageJob.getEndTime()));
                panel.add(new JLabel(pipelineStageJob.getResultStatus()));
                Border border = BorderFactory.createLineBorder(JBColor.BLUE, 3); // 蓝色边框，宽度为3
                panel.setBorder(border);
                panels[j + 1][i + 1] = panel;
            }
        }
        return panels;
    }

    /**
     * @param
     * @return int[] res[0] = row, res[1] = col
     * @author synhard
     * @description 获取表格布局对应的行数和列数
     * @date 2024/5/16 15:37
     */
    private int[] getGridScope(DevProcess devProcess) {
        Pipeline            pipeline          = devProcess.getPipeline();
        List<CodeSource>    codeSourceList    = pipeline.getCodeSourceList();
        List<PipelineStage> pipelineStageList = pipeline.getPipelineStageList();
        int                 col               = codeSourceList.isEmpty() ? 0 : 1 + pipelineStageList.size();
        int                 row               = codeSourceList.size();
        for (PipelineStage pipelineStage : pipelineStageList) {
            int curRow = pipelineStage.getPipelineStageJobList().size();
            if (curRow > row) {
                row = curRow;
            }
        }
        // 多一行作为表头
        return new int[]{row + 1, col};
    }
}